summaryrefslogtreecommitdiff
path: root/src/app/(home)/posts/[slug]/page.client.tsx
diff options
context:
space:
mode:
authorBertrand Yuan <bert.yuan@outlook.com>2025-12-15 23:48:10 +0800
committerBertrand Yuan <bert.yuan@outlook.com>2025-12-15 23:48:10 +0800
commit5b7ccf0b671e2999b62befc729a3e517a0433728 (patch)
tree8bf476dc7c75914c221042546840dc76267366df /src/app/(home)/posts/[slug]/page.client.tsx
initial commit -- the front-end prototype
The initial code is base on Anirudh's work. More to see at: https://github.com/techwithanirudh/shadcn-blog Therefore, the code in this commit is under MIT license.
Diffstat (limited to 'src/app/(home)/posts/[slug]/page.client.tsx')
-rw-r--r--src/app/(home)/posts/[slug]/page.client.tsx57
1 files changed, 57 insertions, 0 deletions
diff --git a/src/app/(home)/posts/[slug]/page.client.tsx b/src/app/(home)/posts/[slug]/page.client.tsx
new file mode 100644
index 0000000..7a97f56
--- /dev/null
+++ b/src/app/(home)/posts/[slug]/page.client.tsx
@@ -0,0 +1,57 @@
+'use client';
+import {
+ UploadIcon as ShareIcon,
+ type UploadIconHandle as ShareIconHandle,
+} from '@/components/icons/animated/upload';
+import { Icons } from '@/components/icons/icons';
+import { Button } from '@/components/ui/button';
+import { cn } from '@/lib/utils';
+import { Comments } from '@fuma-comment/react';
+import { redirect } from 'next/navigation';
+import { useRef } from 'react';
+import { toast } from 'sonner';
+import { useCopyToClipboard } from 'usehooks-ts';
+
+export function Share({ url }: { url: string }): React.ReactElement {
+ const iconRef = useRef<ShareIconHandle>(null);
+ const [_, copyToClipboard] = useCopyToClipboard();
+
+ const onClick = async (): Promise<void> => {
+ await copyToClipboard(`${window.location.origin}${url}`);
+ toast.success('Copied to clipboard!', {
+ icon: <Icons.copied className='size-4' />,
+ description: 'The post link has been copied to your clipboard.',
+ });
+ };
+
+ return (
+ <Button
+ className={cn('group gap-2')}
+ variant={'secondary'}
+ onClick={onClick}
+ onMouseEnter={() => iconRef.current?.startAnimation?.()}
+ onMouseLeave={() => iconRef.current?.stopAnimation?.()}
+ >
+ <ShareIcon className='size-4 hover:bg-transparent' ref={iconRef} />
+ Share Post
+ </Button>
+ );
+}
+
+export function PostComments({
+ slug,
+ className,
+}: { slug: string; className?: string }) {
+ return (
+ <Comments
+ page={slug}
+ className={cn('w-full', className)}
+ auth={{
+ type: 'api',
+ signIn: () => {
+ redirect('/login');
+ },
+ }}
+ />
+ );
+}